package com.example.reflect;

import android.app.Activity;
import android.view.View;

import java.lang.annotation.Annotation;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

public class InjectUtil {

    public static void bind(Activity activity) {
        bindEvent(activity);
    }

    public static void bind(View view) {
        bindEvent(view);
    }

    private static <T> void bindEvent(T t) {
        //获取类
        Class cls = t.getClass();
        //获取对应的所有方法
        Method[] methods = cls.getDeclaredMethods();

        for (Method method : methods) {
            //获取类的所有注解
            Annotation[] annotations = method.getAnnotations();
            for (Annotation annotation : annotations) {
                //获取注解类型
                Class<? extends Annotation> annotationType = annotation.annotationType();

                //是否存在指定类型的注释
                if (!annotationType.isAnnotationPresent(EventType.class)) {
                    continue;
                }

                EventType eventType = annotationType.getAnnotation(EventType.class);
                if (eventType == null) {
                    continue;
                }
                //获取代理的类
                Class<?> listenerType = eventType.listenerType();
                //获取绑定的方法名
                String listenerMethod = eventType.listenerSetter();

                try {
                    Method valueMethod = annotationType.getDeclaredMethod("value");
                    //反射获取所有的findById
                    int[] viewIds = (int[]) valueMethod.invoke(annotation);
                    method.setAccessible(true);

                    //动态创建对应累的代理对象
                    Object listenerProxy = Proxy.newProxyInstance(listenerType.getClassLoader(), new Class[]{listenerType}, new ListenerInvocationHandler<>(t, method));

                    if (viewIds != null) {

                        for (int viewId : viewIds) {
                            View view = null;
                            if (t instanceof Activity) {
                                view = ((Activity) t).findViewById(viewId);
                            }
                            if (t instanceof View) {
                                view = ((View) t).findViewById(viewId);
                            }
                            if (view == null) continue;

                            //获取view的方法名字与点击事件用到的类
                            Method declaredMethod = view.getClass().getMethod(listenerMethod, listenerType);
                            //回调view的点击事件
                            declaredMethod.invoke(view, listenerProxy);
                        }
                    }
                } catch (NoSuchMethodException e) {
                    e.printStackTrace();
                } catch (InvocationTargetException e) {
                    e.printStackTrace();
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                }

            }

        }

    }

}
